package spider.netty;

import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Bean;
import spider.netty.node.NettyChannelNodeManager;
import spider.netty.server.WebSocketServer;
import spider.netty.server.handler.WebSocketServerHandler;
import spider.netty.server.handler.WebSocketServerInitializer;
import spider.netty.support.RedisManager;
import spider.zookeeper.node.NodeManager;

/**
 * SpringNettyApplication
 *
 * @author Archx[archx@foxmail.com]
 * @date 2017/4/8.
 */
@SpringBootApplication
public class SpringNettyApplication implements CommandLineRunner {

    @Override
    public void run(String... strings) throws Exception {
        Thread.currentThread().join();
    }

    @Bean
    @ConfigurationProperties(prefix = "redis")
    public RedisManager redisManager() {
        return new RedisManager();
    }

    @Bean
    @ConfigurationProperties(prefix = "node.manager")
    public NodeManager nodeManager() {
        return new NodeManager();
    }

    @Bean
    @ConfigurationProperties(prefix = "netty.node.manager")
    @ConditionalOnBean({ RedisManager.class, NodeManager.class })
    public NettyChannelNodeManager nettyChannelNodeManager(RedisManager redisManager, NodeManager nodeManager) {
        NettyChannelNodeManager manager = new NettyChannelNodeManager();
        manager.setRedisManager(redisManager);
        manager.setNodeManager(nodeManager);
        return manager;
    }

    @Bean
    @ConditionalOnBean(NettyChannelNodeManager.class)
    public WebSocketServerHandler webSocketServerHandler(NettyChannelNodeManager nettyChannelNodeManager) {
        WebSocketServerHandler handler = new WebSocketServerHandler();
        handler.setNettyChannelNodeManager(nettyChannelNodeManager);
        return handler;
    }

    @Bean
    @ConditionalOnBean(WebSocketServerHandler.class)
    public WebSocketServerInitializer webSocketServerInitializer(WebSocketServerHandler handler) {
        WebSocketServerInitializer initializer = new WebSocketServerInitializer();
        initializer.setWebSocketServerHandler(handler);
        return initializer;
    }

    @Bean
    @ConfigurationProperties(prefix = "web.socket.server")
    @ConditionalOnBean({ WebSocketServerInitializer.class, NodeManager.class })
    public WebSocketServer webSocketServer(WebSocketServerInitializer initializer, NodeManager nodeManager) {
        WebSocketServer server = new WebSocketServer();
        server.setInitializer(initializer);
        server.setNodeManager(nodeManager);
        return server;
    }

    public static void main(String[] args) {
        SpringApplication.run(SpringNettyApplication.class, args);
    }
}
